package com.itcoon.cloud.framework.webmvc.exception.handler;

import org.springframework.util.ReflectionUtils;
import org.springframework.validation.FieldError;

import java.beans.BeanInfo;
import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Optional;

public abstract class ParamsExceptionHandler<E extends Exception> implements GlobalExceptionHandler<E>{

    protected List<String> doParamsEx(List<FieldError> errors, Object target) {
        List<String> parameterExceptionMessages = new ArrayList<>();
        for (FieldError fieldError : errors) {
            parameterExceptionMessages.add(fieldError.getDefaultMessage());
        }
        return parameterExceptionMessages;
    }

    private Field getField(String fieldName,Object target) throws Exception {
        if(fieldName.contains(".")){
            String[] datas = fieldName.split("\\.");
            Object cascadeObj = target;
            for (int i = 0, n = datas.length; i < n; i++) {
                if(i == n - 1){
                    return ReflectionUtils.findField(cascadeObj.getClass(), datas[i]);
                }
                BeanInfo beanInfo = Introspector.getBeanInfo(target.getClass());
                PropertyDescriptor[] propertyDescriptors = beanInfo.getPropertyDescriptors();
                int finalI = i;
                Optional<PropertyDescriptor> propertyOp = Arrays.stream(propertyDescriptors).filter(propertyDescriptor -> propertyDescriptor.getName().equals(datas[finalI])).findAny();
                if(propertyOp.isPresent()){
                    cascadeObj = propertyOp.get().getReadMethod().invoke(cascadeObj);
                }else{
                    throw new IllegalArgumentException("");
                }
            }
        }
        return ReflectionUtils.findField(target.getClass(), fieldName);
    }
}
